/**
 * 公用的数学方法
 */

export class MathUtil {

    private constructor() { }


    /**
     * 获取指定数组中指定个数的随机值
     * @param arr 
     * @param count 
     * */
    static getRandomUniqueNumbers(arr: number[], count: number): number[] {
        if (count > arr.length) {
            throw new Error("请求的数量大于数组长度");
        }

        const result: number[] = [];
        const indices = [...Array(arr.length).keys()];  // 使用扩展运算符直接生成索引数组

        for (let i = 0; i < count; i++) {
            const randomIndex = Math.floor(Math.random() * indices.length);
            result.push(arr[indices[randomIndex]]);

            // 交换法：将随机选中的索引移到数组末尾
            indices[randomIndex] = indices[indices.length - 1];
            indices.pop();
        }

        return result;
    }

    /**
     * 从数组中随机取值
     * @param arr 
     * @returns 
     */
    static randomGetValueFromArr<T>(arr: T[]): T {
        let idx = Math.floor(Math.random() * arr.length);
        return arr[idx];
    }

    /**
     * 范围内随机取值
     * @param min 
     * @param max 
     * @param isInt 是否只需要整数，为 true 时，min、max需要为整数，否则向下取整
     */
    static random(min: number, max: number, isInt: boolean = true): number {
        if (isInt) {
            min = Math.floor(min);
            max = Math.floor(max);
        }
        if (min === max) {
            return min;
        }
        if (min > max) {
            [min, max] = [max, min];
        }
        const delta = max - min;
        if (isInt) {
            return Math.floor(Math.random() * (delta + 1)) + min;
        } else {
            return Math.random() * delta + min;
        }
    }

    /**
     * 范围内随机取整数
     * @param min 
     * @param max 
     * @returns 
     */
    static randomInt(min: number, max: number): number {
        return MathUtil.random(min, max, true);
    }
}